﻿using System;
using System.Collections.Generic;
using System.IdentityModel.Tokens.Jwt;
using System.Linq;
using System.Security.Claims;
using System.Text;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Configuration;
using Microsoft.IdentityModel.Tokens;
using Volo.Abp.DependencyInjection;
using Volo.Abp.Security.Claims;

namespace SmartCity.Shared
{
    /// <summary>
    /// Jwt授权管理类
    /// </summary>
    public class JwtAuthManager : IAuthManager, ITransientDependency
    {
        private readonly IConfiguration _configuration;
        private readonly IHttpContextAccessor _httpContextAccessor;

        public JwtAuthManager(
            IConfiguration configuration,
            IHttpContextAccessor httpContextAccessor)
        {
            _configuration = configuration;
            _httpContextAccessor = httpContextAccessor;
        }

        /// <summary>
        /// 生成票据
        /// </summary>
        /// <param name="userId"></param>
        public string GenerateToken(int userId)
        {
            var claims = new List<Claim>
            {
                new Claim(AbpClaimTypes.UserId, userId.ToString())
            };
            var securityKey = _configuration["Jwt:SecurityKey"] ?? "123456";
            var expirationDays = int.Parse(_configuration["Jwt:ExpirationDays"] ?? "7");
            var symmetricSecurityKey = new SymmetricSecurityKey(Encoding.ASCII.GetBytes(securityKey));
            var signingCredentials = new SigningCredentials(
               symmetricSecurityKey,
               SecurityAlgorithms.HmacSha256);
            var securityToken = new JwtSecurityToken(
                claims: claims,
                expires: DateTime.Now.AddDays(expirationDays),
                signingCredentials: signingCredentials);
            var token = new JwtSecurityTokenHandler().WriteToken(securityToken);
            return token;
        }

        /// <summary>
        /// 获取UserId
        /// </summary>
        public int GetUserId()
        {
            var claim = _httpContextAccessor.HttpContext.User.Claims.FirstOrDefault(c => c.Type == AbpClaimTypes.UserId);
            if (claim == null)
                return default;
            return int.Parse(claim.Value);
        }
    }
}